<template>
  <!--新增或修改用户-->
  <div>
    <n-modal
      :show-icon="false"
      v-model:show="modelInfo.show"
      preset="dialog"
      :title="modelInfo.info.id ? '修改用户' : '新增用户'"
      style="width: 600px"
    >
      <n-form
        :model="modelInfo.info"
        ref="userFormRef"
        label-placement="left"
        :label-width="80"
        class="py-4"
        :rules="userFormRules"
      >
        <n-grid :cols="24">
          <template v-if="modelInfo.info.id === undefined">
            <n-form-item-gi :span="12" label="用户账号" path="loginCode">
              <n-input placeholder="请输入用户账号" v-model:value="modelInfo.info.loginCode" />
            </n-form-item-gi>
            <n-form-item-gi :span="12" label="用户密码" path="password">
              <n-input placeholder="请输入密码" v-model:value="modelInfo.info.password" />
            </n-form-item-gi>
          </template>

          <n-form-item-gi :span="12" label="用户姓名" path="userName">
            <n-input placeholder="请输入用户姓名" v-model:value="modelInfo.info.userName" />
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="部门" path="userOrg">
            <n-tree-select
              style="width: 100%"
              v-model:value="modelInfo.info.userOrg"
              :options="deptTree"
              label-field="name"
              key-field="id"
              children-field="children"
            />
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="职位名称" path="userPosition">
            <n-select
              placeholder="请选择用户职位"
              v-model:value="modelInfo.info.userPosition"
              :options="postCodeList"
            />
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="角色" path="userRole">
            <n-select
              placeholder="请选择用户角色"
              v-model:value="modelInfo.info.userRole"
              :options="roleCodeList"
              multiple
            />
          </n-form-item-gi>
          <n-form-item-gi :span="24" label="数据范围" path="dataScope">
            <n-tree
              ref="menuTreeRef"
              style="width: 100%; border: 1px solid rgba(229, 231, 235); border-radius: 5px"
              checkable
              cascade
              :data="deptTree"
              label-field="name"
              key-field="id"
              :checked-keys="deptTreeSelectedKeys"
              @update:checked-keys="
                (keys) => {
                  deptTreeSelectedKeys = keys;
                }
              "
              @update:indeterminate-keys="
                (keys) => {
                  deptTreeHalfSelectedKeys = keys;
                }
              "
            />
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="手机号码" path="mobile">
            <n-input placeholder="请输入手机号码" v-model:value="modelInfo.info.mobile" />
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="电子邮箱" path="email">
            <n-input placeholder="请输入电子邮箱" v-model:value="modelInfo.info.email" />
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="用户性别" path="sex">
            <n-radio-group v-model:value="modelInfo.info.sex" name="radiogroup">
              <n-space>
                <n-radio v-for="item in genderList" :key="item.value" :value="item.value">
                  {{ item.label }}
                </n-radio>
              </n-space>
            </n-radio-group>
          </n-form-item-gi>
          <n-form-item-gi :span="12" label="账号状态" path="status">
            <n-radio-group v-model:value="modelInfo.info.status">
              <n-space>
                <n-radio v-for="item in stateTypeList" :key="item.value" :value="item.value">
                  {{ item.label }}
                </n-radio>
              </n-space>
            </n-radio-group>
          </n-form-item-gi>
          <n-form-item-gi :span="24" label="备注" path="remark">
            <n-input type="textarea" v-model:value="modelInfo.info.remark" />
          </n-form-item-gi>
        </n-grid>
      </n-form>
      <template #action>
        <n-space>
          <n-button @click="modelInfo.show = false">取消</n-button>
          <n-button type="info" @click="onAddOrEditUser">确认</n-button>
        </n-space>
      </template>
    </n-modal>
  </div>
</template>

<script lang="ts" setup>
  import { reactive, ref } from 'vue';
  import { getPostByParamsApi } from '@/api/system/post';
  import {
    debounce,
    deleteNullChildren,
    getArrDiff,
    getArrIntersection,
    getTreeBaseData,
    structureSelectOptions,
  } from '@/utils';
  import Regex from '@/utils/regex';
  import { getRoleByParamApi } from '@/api/system/role';
  import { useInitDict } from '@/hooks/dictHooks';
  import { addUserApi, modifyUserApi } from '@/api/system/user';

  import { messageHooks } from '@/hooks/baseHooks';
  import { getDeptTreeApi } from '@/api/system/dept';

  const { message } = messageHooks();
  const emit = defineEmits(['add:success', 'update:success']);

  const userFormRef = ref();
  const userFormRules = reactive({
    loginCode: [
      { required: true, message: '请输入账号', trigger: 'blur' },
      { pattern: Regex.loginCodeReg, message: '请输入英文或数字组成的账号', trigger: 'blur' },
    ],
    password: [
      { required: true, message: '请输入账号', trigger: 'blur' },
      {
        pattern: Regex.passwordReg,
        message: '密码必须包含数字、英文字母，长度在8~16位',
        trigger: 'blur',
      },
    ],
    userOrg: [{ required: true, message: '请选择用户部门', trigger: 'blur' }], // 部门id
    userRole: [{ required: true, type: 'array', message: '请选择用户角色', trigger: 'blur' }], // 用户角色
    userName: [
      { required: true, message: '请输入正确的名称', trigger: 'blur' },
      { pattern: Regex.userNameReg, message: '姓名只能输入中文', trigger: 'blur' },
    ], // 用户昵称
    mobile: [
      { required: false, pattern: Regex.mobileReg, message: '手机号格式不正确', trigger: 'blur' },
    ], // 手机号
    email: [
      {
        required: false,
        pattern: Regex.emailReg,
        message: '邮箱格式不正确',
        trigger: 'blur',
      },
    ], // 邮箱
    userPosition: [{ required: true, message: '请选择用户职位', trigger: 'blur' }], // 职位
  });

  const postCodeList = ref([]);
  const roleCodeList = ref([]);

  //部门树
  const deptTree = ref([]);
  const deptTreeSelectedKeys = ref([]);
  const deptTreeHalfSelectedKeys = ref([]);

  let modelInfo = reactive({
    show: false,
    info: {},
  }); //显示新增修改弹窗

  //初始化数据字典
  const { stateTypeList, genderList } = useInitDict({
    STATUS_TYPE: 'stateTypeList',
    GENDER: 'genderList',
  });

  function resetModelInfo() {
    modelInfo.show = false;
    modelInfo.info = {
      id: undefined,
      userOrg: undefined, // 部门id
      loginCode: undefined, // 登录Id
      password: '88888888', // 密码
      userName: undefined, // 用户昵称
      mobile: undefined, // 手机号
      email: undefined, // 邮箱
      sex: 'MAN', // 性别
      avatar: undefined, // 头像
      status: 'ENABLE', // 用户状态
      userPosition: undefined, // 职位
      remark: undefined, // 备注
      userRole: [], // 角色ids
      dataScope: [], // 数据范围
    };

    deptTreeSelectedKeys.value = [];
    deptTreeHalfSelectedKeys.value = [];

    getPostByParamsApi().then((res) => {
      if (res && res.code === 'A00000') {
        postCodeList.value = structureSelectOptions(res.data, {
          label: 'positionName',
          value: 'id',
        });
      }
    });
    getRoleByParamApi({}).then((res) => {
      if (res && res.code === 'A00000') {
        roleCodeList.value = structureSelectOptions(res.data, {
          label: 'roleName',
          value: 'id',
        });
      }
    });
  }

  const onAddOrEditUser = debounce(function () {
    // emit('success');
    // return;
    userFormRef.value.validate((errors) => {
      if (!errors) {
        let params = {
          ...modelInfo.info,
          dataScope: [...deptTreeSelectedKeys.value, ...deptTreeSelectedKeys.value],
        };
        if (params.id === undefined) {
          // 新增用户
          addUserApi(params).then((res) => {
            if (res.code === 'A00000') {
              message.success(res.msg);
              modelInfo.show = false;
              emit('add:success');
            } else {
              message.error(res.msg);
            }
          });
        } else {
          // 修改用户
          modifyUserApi(params).then((res) => {
            if (res.code === 'A00000') {
              message.success(res.msg);
              modelInfo.show = false;
              emit('update:success');
            } else {
              message.error(res.msg);
            }
          });
        }
      }
    });
  });

  //打开新增用户页面
  function onOpenAddUser() {
    resetModelInfo();

    onGetDeptTreeData();

    modelInfo.show = true;
  }

  //点击修改按钮
  function onOpenEditUser(record: Recordable) {
    resetModelInfo();

    onGetDeptTreeData(function () {
      const subTree = getTreeBaseData(deptTree.value);

      record.dataScope = record.dataScope || [];

      deptTreeSelectedKeys.value = getArrIntersection(record.dataScope, subTree);

      let diff = getArrDiff(record.dataScope, deptTreeSelectedKeys.value);

      deptTreeHalfSelectedKeys.value = diff;

      modelInfo.info = record;
      modelInfo.show = true;
    });
  }

  /**
   * 获取部门tree数据
   */
  function onGetDeptTreeData(callback?: Function) {
    getDeptTreeApi({}).then((res) => {
      if (res && res.code === 'A00000') {
        deptTree.value = deleteNullChildren(res.data);
        if (callback) {
          callback();
        }
      }
    });
  }

  defineExpose({
    onOpenAddUser,
    onOpenEditUser,
  });
</script>

<style scoped></style>
